﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Net.NetworkInformation;
using System.Threading;
using System.Runtime.InteropServices;
using System.Net;
using System.Data;
using System.Collections.ObjectModel;
using NetViewer.Models;

namespace NetViewer
{
    /// <summary>
    /// MainWindow.xaml 的交互逻辑
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }
        [DllImport("ws2_32.dll", CharSet = CharSet.Unicode)]
        private static extern int inet_addr(string cp);

        [DllImport("IPHLPAPI.dll")]
        private static extern int SendARP(Int32 DestIP, Int32 ScrIP, ref Int64 pMacAddr, ref Int32 PhyAddrLen);

        private ObservableCollection<AddressModel> aData = new ObservableCollection<AddressModel>();
        private ObservableCollection<AdapterModel> adaData = new ObservableCollection<AdapterModel>();
        private void Grid_Loaded(object sender, RoutedEventArgs e)
        {
            NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();
            foreach (var netWork in nics)
            {
                AdapterModel am = new AdapterModel();
                am.Name = netWork.Name;
                IPInterfaceProperties ip = netWork.GetIPProperties();

                foreach (var adapter in ip.UnicastAddresses)
                {   
                    if (adapter.PrefixLength == 64)
                        am.IPv6 = adapter.Address.ToString();
                    else
                        am.IPv4 = adapter.Address.ToString();
                }
                adaData.Add(am);

                foreach (var gatway in ip.GatewayAddresses)
                {
                    tbGatway.Text = gatway.Address.ToString();//获取网关
                }
            }
            dgvInfo.AutoGenerateColumns = false;
            dgvInfo.ItemsSource = aData;
            dgAda.AutoGenerateColumns = false;
            dgAda.ItemsSource = adaData;
        }
        int i = 0;
        

        delegate void SetpbCallBack(int val);
        delegate void SetNetCallBack(string name, string ip, string mac);
        
        private void _myPing_PingCompleted(object sender, PingCompletedEventArgs e)
        {
            if (e.Reply.Status == IPStatus.Success)
            {
                string ip = e.Reply.Address.ToString();
                string name = "";
                try
                {
                    IPHostEntry nds = Dns.GetHostEntry(IPAddress.Parse(ip));
                    //Dns.GetHostByAddress(IPAddress.Parse(ip));
                    name = nds.HostName;
                }
                catch
                {
                    name = "0x";
                }

                string Mac = "";
                try
                {
                    int ldest = inet_addr(ip); //将IP地址从 点数格式转换成无符号长整型
                    long macinfo = new long();
                    int len = 6;
                    //SendARP函数发送一个地址解析协议(ARP)请求获得指定的目的地IPv4地址相对应的物理地址
                    SendARP(ldest, 0, ref macinfo, ref len);
                    string TmpMac = Convert.ToString(macinfo, 16).PadLeft(12, '0');//转换成16进制　　注意有些没有十二位
                    Mac = TmpMac.Substring(0, 2).ToUpper();//
                    for (int i = 2; i < TmpMac.Length; i = i + 2)
                    {
                        Mac = TmpMac.Substring(i, 2).ToUpper() + "-" + Mac;
                    }
                }
                catch (Exception Mye)
                {
                    Mac = "获取远程主机的MAC错误：" + Mye.Message;
                }

                SetNet(name, ip, Mac);
            }
            Dispatcher.BeginInvoke(new Action(delegate
            {
                pbIP.Value++;
            }));
        }
        private void btnStart_Click(object sender, RoutedEventArgs e)
        {
            pbIP.Value = 0;
            i = 0;
            try
            {
                string gatway = tbGatway.Text;
                gatway = gatway.Remove(gatway.Length - 1);

                Thread tdGetIP = new Thread(() => {
                    for (; i <= 254; i++)
                    {
                        string ip = gatway + i.ToString();
                        ThreadGetIP(ip);
                    }
                });
                tdGetIP.IsBackground = true;
                tdGetIP.Start();

            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.ToString());
            }
        }
        private void btnClear_Click(object sender, RoutedEventArgs e)
        {
            aData.Clear();
            pbIP.Value = 0;
        }

        #region 类
        private void SetNet(string name, string ip, string mac)
        {
            Dispatcher.BeginInvoke(new Action(delegate
            {
                aData.Add(new AddressModel { Name = name, IP = ip, MAC = mac });
            }));
        }

        private void ThreadGetIP(object ip)
        {
            Ping myPing = new Ping();
            myPing.PingCompleted += new PingCompletedEventHandler(_myPing_PingCompleted);

            string pingIP = ip.ToString();
            try
            {
                myPing.SendAsync(pingIP, 1000);
            }
            catch
            {
                pbIP.Value++;
            }
        }
        #endregion
    }
}
